package com.fub.positioning;

import java.util.ArrayList;
import java.util.List;

import android.content.Context;
import android.database.Cursor;

import com.fub.guidance.Point;
import com.fub.util.database.databaseHelper.AccessPointsDatabaseManager;
import com.fub.util.database.databaseHelper.FingerprintDatabaseManager;

public class ReferencePointDAO {
	private static int SSID_Position = 2;
	private static int SS_POSITION = 3;
	private FingerprintDatabaseManager fingerprintDatabaseManager;
	private AccessPointsDatabaseManager accessPointsDatabaseManager;

	/**
	 * Constructs a new data access object for reference points.
	 * 
	 * @param context
	 *            the application context
	 */
	public ReferencePointDAO(Context context) {
		this.fingerprintDatabaseManager = new FingerprintDatabaseManager(context);
		this.accessPointsDatabaseManager = new AccessPointsDatabaseManager(context);
	}

	/**
	 * Returns all reference points of a building from database.
	 * 
	 * @param buildingID
	 *            the id of the building
	 * @return all reference points of a building from database
	 */
	public List<ReferencePoint> getReferencePoints(String buildingID) {
		List<ReferencePoint> referencePoints = new ArrayList<ReferencePoint>();
		String query = String.format("Select * FROM %s WHERE %s = '%s'",
				FingerprintDatabaseManager.TABLE_NAME_REFERENCE_POINTS,
				FingerprintDatabaseManager.COL_BUILDING_ID, buildingID);
		Cursor cursor = this.fingerprintDatabaseManager.getReadableDatabase()
				.rawQuery(query, null);
		while (cursor.moveToNext()) {
			String bId = cursor.getString(1);
			String locationId = cursor.getString(2);
			int x = cursor.getInt(3);
			int y = cursor.getInt(4);
			int z = cursor.getInt(5);

			Measurement measurement = readAccessPoints(bId, locationId);
			ReferencePoint rp = new ReferencePoint(bId, locationId, new Point(
					x, y, z), measurement);
			referencePoints.add(rp);
		}
		cursor.close();
		return referencePoints;
	}

	private Measurement readAccessPoints(String bid, String locationId) {
		Measurement measurement = new Measurement();
		String query = String.format(
				"SELECT * FROM %s WHERE %s = '%s' AND %s = '%s'",
				AccessPointsDatabaseManager.TABLE_NAME_ACCESS_POINTS,
				AccessPointsDatabaseManager.BUILDING_ID_COL, bid,
				AccessPointsDatabaseManager.COL_LOCATION_ID, locationId);
		Cursor cursor = this.accessPointsDatabaseManager.getReadableDatabase()
				.rawQuery(query, null);
		while (cursor.moveToNext()) {
			String ssid = cursor.getString(SSID_Position);
			String ss = cursor.getString(SS_POSITION);
			measurement.putSignalStrength(ssid, Integer.parseInt(ss));
		}

		return measurement;
	}

	/**
	 * Inserts a reference point into the database.
	 * 
	 * @param referencePoint
	 *            the reference point.
	 */
	public void insertReferencePoint(ReferencePoint referencePoint) {
		String query = String
				.format("INSERT INTO %s (%s,%s,%s,%s,%s) VALUES ('%s','%s','%d','%d','%d')",
						FingerprintDatabaseManager.TABLE_NAME_REFERENCE_POINTS,
						FingerprintDatabaseManager.COL_BUILDING_ID,
						FingerprintDatabaseManager.COL_LOCATION_ID,
						FingerprintDatabaseManager.COL_X,
						FingerprintDatabaseManager.COL_Y,
						FingerprintDatabaseManager.COL_Z, referencePoint
								.getBuildingId(), referencePoint.getLocation(),
						referencePoint.getPosition().getX(), referencePoint
								.getPosition().getY(), referencePoint
								.getPosition().getZ());
		this.fingerprintDatabaseManager.getWritableDatabase().execSQL(query);
		for (String ssid : referencePoint.getMeasurement().getSSids()) {
			String subQuery = String.format(
					"INSERT INTO %s VALUES ('%s','%s','%s','%s')",
					AccessPointsDatabaseManager.TABLE_NAME_ACCESS_POINTS,
					referencePoint.getBuildingId(), referencePoint
							.getLocation(), ssid, referencePoint
							.getMeasurement().getSingnalStrength(ssid));
			this.accessPointsDatabaseManager.getWritableDatabase().execSQL(subQuery);
		}
	}

	/**
	 * Deletes all reference points of a building from database.
	 * 
	 * @param buildingID
	 *            the id of the building
	 */
	public void deleteAll(String buildingID) {
		String query = String.format("DELETE FROM %s WHERE %s = '%s'",
				FingerprintDatabaseManager.TABLE_NAME_REFERENCE_POINTS,
				FingerprintDatabaseManager.COL_BUILDING_ID, buildingID);
		this.fingerprintDatabaseManager.getWritableDatabase().execSQL(query);

	}

	/**
	 * Deletes all reference points from database
	 */
	public void deleteAll() {
		String query = String.format("DELETE FROM %s",
				FingerprintDatabaseManager.TABLE_NAME_REFERENCE_POINTS);
		this.fingerprintDatabaseManager.getWritableDatabase().execSQL(query);

	}
}
